#include <iostream>
#include <list>
#include <map>

#include "Reglesbase.h"

// *********************
// @ SERVER UNIQUEMENT *
// *********************


class Carte;
class Camp;
struct Client;

class Reglesbase;

using namespace std;


// *********************
// Classe gerant toutes les donnees et fonctions specifique a une partie
//
// Les regles sont specifiees ici
// L'appel des fonctions pour la partie se trouve ici :
// 		ex : T1 attaque T2
// 			 T1 donne un de a T2
// 			 ...
// *********************
class Partie
{
	private:
		Carte* map;
		Camp* camps;
		//std::vector<Territoire*> territoires; OUI/NON ???
	
		Reglesbase regles;
		int joueurActuel;

		// Liste des clients joueurs;
		std::map<string, Client * > clients;
		int nombreJoueurs;

		int T1, T2;
		
		// ************************

		sf::TcpListener * listener;
		sf::SocketSelector * selector;

		// Si nombre de clients < nombreJoueur, les autres joueurs sont des IA

	public:

		Partie( int nombreJoueurMax, sf::TcpListener * listen, sf::SocketSelector * select ); // Maximum 8
		~Partie();
	
		/*
		* Renvoie la carte generee aleatoirement, sans iles,
		* chaque camp a le meme nombre de territoire,
		* avec chaque territoire qui possede une liste de voisins.
		*/
		void genererCarte(int nbTparJ);

		/*
		* Renvoie le nombre de territoires par joueur a assigner
		* en debut de partie.
		*/
		int nbTParJoueur(int nbJ);

		/*
		* Renvoie le camp du dernier joueur en vie, NULL sinon.
		*/
		bool uniqueJoueur();

		/*
		* Deploie aleatoirement et equitablement les des sur chaque territoire de chaque camps en debut de partie.
		*/
        void deploiAleaDes(Camp &c, int nbDesADeploi, bool vite);

		/*
		 * Ajoute un client si possible
		 * Si bool == false -> Partie pleine
		 */
		bool ajouterJoueur( std::pair<string,Client *> client );

		/*
		 * Enleve un joueur,
		 * Si partie en cours remplacement par un IA
		 * Renvoie un true si nombre joueur non IA > 0
		 */
		bool retirerJoueur( std::pair<string,Client *> client );


		/*
		 * Dans cette fonction il y a tout le deroulement de
		 * la partie. La boucle PRINCIPALE
		 */
		void run();

		void setReady( string nomJoueur );
		bool allReady();
		void sendMap();

		int getNbJoueur();
		int getNbJoueurMax();

		void infoNewJoueur( pair<string, Client*> client);
		void combatIAsimple(Camp* c);
		void JoueurSuivant();
};
